export default class TagService {
    context;
    rowTags; //TODO 进行标签的状态维护
    columnTags;
    constructor(context) {
        this.context = context;
    }
    get headerService() {
        return this.context.headerService;
    }
    get hot() {
        return this.context.hot;
    }
    get hyper() {
        return this.context.hyper;
    }
    get formulaService() {
        return this.context.formulaService;
    }
    get gridService() {
        return this.context.gridService;
    }
    destroy() {
        this.context = null;
    }
    /**
     * 追溯当前单元格的聚合数据来源
     * @param tagName
     * @param rows
     */
    getTagCountStepByCell(row, col) {
        const displayData = this.context.getCpasTableGrid("display").data;
        const sourceData = this.context.getCpasTableGrid().data;
        const headerColumn = this.context.headerService.headerColumn;
        if (!displayData || !sourceData) {
            return {
                error: "未获取到数据源",
                msg: "",
                data: [],
            };
        }
        const rowConfigColIndex = sourceData[0].length - 1;
        const rowConfig = JSON.parse(sourceData[row][rowConfigColIndex]);
        const columnConfig = headerColumn[col].config;
        if (!rowConfig.r_polymeric && !columnConfig.c_polymeric) {
            return {
                error: "",
                msg: "既不是行聚合也不是列聚合",
                data: [],
            };
        }
        if (columnConfig.p_exclude) {
            return {
                error: "",
                msg: "该列是豁免列",
                data: [],
            };
        }
        let type = "";
        const tagsCell = [];
        // 行聚合
        if (rowConfig.r_polymeric) {
            type = "行聚合";
            const tags = rowConfig.r_polymeric.tags;
            for (let i = 0; i < sourceData.length; i++) {
                const row = sourceData[i];
                const rowConfig = JSON.parse(row[rowConfigColIndex]);
                const rTags = rowConfig["r_tag"];
                if (rTags) {
                    const hasCommonValue = tags.some((value) => rTags.includes(value));
                    if (hasCommonValue) {
                        tagsCell.push({
                            rmap: row[0],
                            cmap: sourceData[0][col],
                            value: displayData[i][col],
                            type: rowConfig["w"] || "normal",
                        });
                    }
                }
            }
        }
        if (columnConfig.c_polymeric) {
            type = type ? type + "|列聚合" : "列聚合";
            const tags = columnConfig.c_polymeric.tags;
            for (let i = 0; i < headerColumn.length; i++) {
                const columnConfig = headerColumn[i].config;
                const cTag = columnConfig["c_tag"];
                if (cTag) {
                    const hasCommonValue = tags.some((value) => cTag.includes(value));
                    if (hasCommonValue) {
                        tagsCell.push({
                            rmap: sourceData[row][0],
                            cmap: sourceData[0][i],
                            value: displayData[row][i],
                            type: "normal", //列标签没有 z j
                        });
                    }
                }
            }
        }
        return {
            error: "",
            msg: type,
            data: tagsCell,
        };
    }
    setRowTags(tagName, rows) {
        const gridData = this.context.data;
        const lastHeader = this.context.headerService.lastHeader;
        for (let i = 0; i < rows.length; i++) {
            const row = rows[i];
            //取出行的配置信息
            const config = JSON.parse(gridData[row][lastHeader]);
            if (!config.r_tag) {
                config.r_tag = [];
            }
            //新增加入的tag
            config.r_tag.push(tagName);
            //设置到行配置中
            gridData[row][lastHeader] = JSON.stringify(config);
        }
        const hot = this.context.hot;
        hot.suspendRender();
        hot.updateData(gridData);
        this.refreshTagColumn(this.context, rows);
        hot.resumeRender();
    }
    setColumnTags(tagName, cols, callback) {
        const gridData = this.context.data;
        const headJson = this.context.headerService.headJson;
        for (let i = 0; i < cols.length; i++) {
            const col = cols[i];
            //取出列配置信息
            const config = this.context.headerService.getHeaderConfigByIndex(this.context.headerService.headJson, col).config;
            let _c_tag = [];
            if (config.c_tag) {
                _c_tag = config.c_tag;
            }
            //新增加入的tag
            _c_tag.push(tagName);
            //设置到列配置信息中
            const update_config_headerJson = this.context.headerService.updateHeaderConfigByIndex(headJson, col, {
                c_tag: _c_tag,
            });
            callback(update_config_headerJson);
        }
        this.context.hot.updateData(gridData);
    }
    getAllTag(type) {
        const cellMetas = this.context.hot.getCellsMeta();
        const set = new Set();
        for (let i = 0; i < cellMetas.length; i++) {
            const cellMeta = cellMetas[i];
            if (type === "row" && cellMeta.r_tag) {
                //获取行的所有标签
                for (let j = 0; j < cellMeta.r_tag.length; j++) {
                    const r_tag = cellMeta.r_tag[j];
                    if (!r_tag.includes("TOP--")) {
                        set.add(r_tag);
                    }
                }
            }
            if (type === "column" && cellMeta.c_tag) {
                //获取列的所有标签
                for (let j = 0; j < cellMeta.c_tag.length; j++) {
                    const c_tag = cellMeta.c_tag[j];
                    if (!c_tag.includes("LEFT--")) {
                        set.add(c_tag);
                    }
                }
            }
        }
        return Array.from(set);
    }
    /**
     * 行列设置权重
     * weightType: z 其中 0 , j 减  -1
     */
    setWeight(type, weightType, currentRange) {
        //如果单个设置状态
        const { rows, cols } = this.gridService.getRangeRowsAndColumn(currentRange);
        const gridData = this.context.data;
        let w = weightType;
        if (type === "row") {
            for (let i = 0; i < rows.length; i++) {
                const row = rows[i];
                const config = JSON.parse(gridData[row][this.headerService.lastHeader]);
                //如果之前选中过，在点击取消
                if (config["w"] === weightType) {
                    config["w"] = "";
                }
                else {
                    config["w"] = weightType;
                }
                if (i === 0) {
                    w = config["w"];
                }
                gridData[row][this.headerService.lastHeader] = JSON.stringify(config);
            }
        }
        else {
            //TODO 是否需要列权重运算？需求上应该没有.预留位置
        }
        this.context.menuToolRef.current.setState({ weightType: w });
        //当需要刷新cellMeta的时候,需要执行updateData
        this.hot.updateData(gridData);
        this.formulaService.refreshAllPolymeric();
        // this.formulaService.refreshAllPolymericRow();
    }
    /**
     * 设置行标签列展示
     */
    async isShowTagColumn(isShow, gridRef, isForceRefresh = false) {
        const gridService = gridRef.gridService;
        const headerRootColumn = gridRef.headerService.headJson;
        const { key, label } = headerRootColumn[headerRootColumn.length - 2]; // 倒数第二个, 最后一个是config列;
        // 插列
        if (isShow) {
            // 获取当前表格行配置的标签信息;
            // addColumn(type, isCopy, columnKey)
            if (label === "行标签") {
                return;
            }
            await gridService.addColumn("right", false, key, {
                columnName: "行标签",
                isReadOnly: true,
                isRuntime: true,
                columnType: "text",
                width: 250,
            }, false);
            // setTimeout(() => {
            this.refreshTagColumn(gridRef, null, isForceRefresh);
            // }, 2000);
        }
        else {
            // 删列
            if (label === "行标签") {
                gridService.removeColumn(key);
            }
        }
    }
    /**
     * 刷新标签列
     * @param gridRef
     */
    refreshTagColumn(gridRef, rows, isForceRefresh = false) {
        if (!this.context.menuToolRef.current?.state.showRowTag &&
            !isForceRefresh) {
            return;
        }
        const hot = gridRef.hot;
        let data = [];
        let tagsList = [];
        if (hot) {
            data = hot.getSourceData();
            const configIndex = data[0].length - 1;
            const tagColumnIndex = data[0].length - 2;
            // 如果row存在, 指定了刷新行
            if (rows) {
                rows.forEach((row) => {
                    const specialRow = data[row];
                    const rowConfig = JSON.parse(specialRow[configIndex]);
                    tagsList.push(this.getTagsString("row", rowConfig));
                });
            }
            else {
                //获取tag列数据
                tagsList = data.map((item) => {
                    const rowConfig = JSON.parse(item[configIndex]);
                    return this.getTagsString("row", rowConfig);
                });
            }
            // 赋值 tag列数据
            hot.suspendRender();
            // 如果row存在, 指定了刷新行
            if (rows) {
                rows.forEach((row, index) => {
                    hot.setSourceDataAtCell(row, tagColumnIndex, tagsList[index]);
                    this.context.data[row][tagColumnIndex] = tagsList[index];
                    hot.setCellMeta(row, tagColumnIndex, "comment", {
                        value: tagsList[index],
                        readOnly: true,
                    });
                });
            }
            else {
                data.forEach((item, index) => {
                    hot.setSourceDataAtCell(index, tagColumnIndex, tagsList[index]);
                    this.context.data[index][tagColumnIndex] = tagsList[index];
                    hot.setCellMeta(index, tagColumnIndex, "comment", {
                        value: tagsList[index],
                        readOnly: true,
                    });
                });
            }
            hot.resumeRender();
            const sourceData = hot.getSourceData();
            console.log(sourceData);
        }
    }
    getTagsString(type, config) {
        let polymeric_info = this.getPolymericString(type, config);
        let tags_info = "";
        if (type === "row") {
            if (config.r_tag) {
                tags_info = `[${config.r_tag
                    .filter((tag) => {
                    return !tag.startsWith("TOP"); //过滤聚合行标签
                })
                    .join()}]`;
            }
        }
        if (polymeric_info && tags_info) {
            return polymeric_info + "," + tags_info;
        }
        else if (polymeric_info) {
            return polymeric_info;
        }
        else {
            return tags_info;
        }
    }
    getPolymericString(type, config) {
        const tagTypeMap = {
            SUM: "求和",
            AVERAGE: "平均",
            MAX: "最大",
            MIN: "最小",
        };
        if (type === "row") {
            if (config.r_polymeric) {
                const r_polymeric = config.r_polymeric;
                let tagType = "标签聚合"; //  行聚合  // 标签聚合
                let countType = r_polymeric.type;
                let tags = r_polymeric.tags;
                if (tags.length === 1 && tags[0].startsWith("TOP")) {
                    tagType = "行聚合";
                }
                if (tagType === "行聚合") {
                    return `{${tagType}:${tagTypeMap[countType] || "未知"}}}`;
                }
                else {
                    return `{${tagType}:${tagTypeMap[countType] || "未知"}:[${tags.join()}]}`;
                }
            }
        }
        return "";
    }
    /**
     * 设置调整列的配置
     * @param isSet true设置, false取消
     * @param key
     * @param tzGroup 组号
     * @returns
     */
    setTZPolymericExclude(isSet, key, tzGroup, param) {
        if (typeof tzGroup === "undefined") {
            return;
        }
        const headerColumn = this.context.headerService.headerColumn;
        const resGroup = headerColumn.filter((item) => item?.config?.tzGroup === tzGroup && item.key !== key);
        if (!resGroup.length || !resGroup.length) {
            return;
        }
        resGroup.forEach((item, index) => {
            //设置配置
            if (isSet) {
                this.headerService.updateNodeByKey(item.key, this.headerService.headJson, param, true);
            }
            else {
                //取消配置
                this.headerService.updateNodeByKey(item.key, this.headerService.headJson, {}, true, param);
            }
        });
    }
    /**
     * 设置豁免/不参与 行,列
     * type :  row 行 , column 列
     * excludeType： p是豁免， c是不参与
     * @param currentRange
     */
    setPolymericExclude(type, excludeType) {
        const currentRecord = this.context.state.currentRecord;
        //行豁免 , 设置列表头
        if (type === "row") {
            if (!currentRecord) {
                this.context.menuToolRef.current.showErrorNotify("请选择表头进行操作");
                return;
            }
            if (!currentRecord.key) {
                this.context.menuToolRef.current.showErrorNotify("请选择表头进行操作");
                return;
            }
            const col = currentRecord.coords.col;
            const headerColumn = this.context.headerService.headerColumn;
            const selectCol = headerColumn[col];
            const { key, config } = selectCol;
            const tzGroup = config ? config?.tzGroup : undefined;
            const currentPe = excludeType === "p" ? config["p_exclude"] : config["c_exclude"];
            if (!currentPe) {
                const peInfo = excludeType === "p"
                    ? { p_exclude: true, c_exclude: false }
                    : { c_exclude: true, p_exclude: false };
                this.headerService.updateNodeByKey(key, this.headerService.headJson, peInfo, true);
                this.setTZPolymericExclude(true, key, tzGroup, peInfo);
            }
            else {
                const excludeT = excludeType === "p" ? ["p_exclude"] : ["c_exclude"];
                this.headerService.updateNodeByKey(key, this.headerService.headJson, {}, true, excludeT);
                this.setTZPolymericExclude(false, key, tzGroup, excludeT);
            }
            this.headerService.headerCompute(this.headerService.headJson);
            const pExclude = !(currentPe === true);
            if (excludeType === "p") {
                this.context.menuToolRef.current.setState({
                    pExclude,
                    cExclude: false,
                });
            }
            if (excludeType === "c") {
                this.context.menuToolRef.current.setState({
                    cExclude: pExclude,
                    pExclude: false,
                });
            }
        }
        else {
            // TODO 列聚合豁免
        }
    }
    set getTag(currentRange) {
        console.log(this.gridService.getRangeRowsAndColumn(currentRange));
        console.log(this.hot.getCellsMeta());
        // console.log(hotRef.current.getCellMetaAtRow(currentRecord.coords.row));
    }
    /**
     * 删除列标签
     * @param removedTag
     */
    handleDeleteColLabel(removedTag) {
        let { rows, cols } = this.gridService.getRangeRowsAndColumn(this.context.state.currentRange);
        const headJson = this.context.headerService.headJson;
        const headerColumn = this.context.headerService.headerColumn;
        const tableColCount = this.context.hot.countCols();
        for (let i = 0; i < cols.length; i++) {
            const col = cols[i];
            const colData = headerColumn[col];
            const key = colData.key;
            const config = colData?.config;
            // 删除数组中的 对应标签
            const tag_arr = config?.c_tag;
            if (tag_arr && tag_arr.length > 0) {
                let removed_tag_arr = tag_arr.filter((item) => item != removedTag);
                let isRemove = false;
                if (removed_tag_arr.length === 0) {
                    isRemove = true;
                }
                // const update_config_headerJson =
                //   this.context.headerService.updateHeaderConfigByIndex(headJson, col, {
                //     c_tag: removed_tag_arr,
                //   });
                const update_config_headerJson = isRemove
                    ? this.context.headerService.updateNodeByKey(key, headJson, {}, true, ["c_tag"])
                    : this.context.headerService.updateNodeByKey(key, headJson, {
                        c_tag: removed_tag_arr,
                    }, true);
                this.context.headerService.headerCompute(update_config_headerJson);
            }
        }
        //重新赋值一下所有标签
        this.context.menuToolRef.current.setState({
            allColumnTags: [...this.context.tagService.getAllTag("column")],
        });
        //刷新公式
        //this.context.formulaService.refreshAllPolymericRow();
        //this.context.formulaService.refreshAllPolymericColumn();
        //刷新公式@todo迁移后台
        this.formulaService.refreshAllPolymeric();
    }
    /**
     * 删除行标签
     * @param removedTag
     */
    handleDeleteRowLabel(removedTag) {
        let { rows, cols } = this.gridService.getRangeRowsAndColumn(this.context.state.currentRange);
        const gridData = this.context.data;
        const lastHeader = this.context.headerService.lastHeader;
        const tableRowCount = this.hot.countRows();
        for (let i = 0; i < rows.length; i++) {
            const row = rows[i];
            const config = JSON.parse(gridData[row][lastHeader]);
            // 删除数组中的 对应标签
            const tag_arr = config.r_tag;
            if (tag_arr && tag_arr.length > 0) {
                const removed_tag_arr = tag_arr.filter((item) => item != removedTag);
                config.r_tag = removed_tag_arr;
                if (removed_tag_arr.length === 0)
                    delete config.r_tag;
                gridData[row][lastHeader] = JSON.stringify(config);
            }
        }
        // 由于 cellsHook 只会合并到cellMeta ， 已有的没办法通过合并进去，所以需要重新赋值 cellMeta.
        // 批量清空cellMeta中的属性
        this.hot.suspendRender();
        const all_columns = this.headerService.headerColumn;
        for (let k = 0; k < all_columns.length; k++) {
            const colIndex = k;
            for (let j = 0; j < rows.length; j++) {
                const rowIndex = rows[j];
                if (gridData[rowIndex][lastHeader].r_tag) {
                    this.hot.setCellMetaObject(rowIndex, colIndex, {
                        r_tag: gridData[rowIndex][lastHeader].r_tag,
                    });
                }
                else {
                    this.hot.removeCellMeta(rowIndex, colIndex, "r_tag");
                }
            }
        }
        this.hot.resumeRender();
        //数据同步
        //this.context.data = gridData;
        this.hot.suspendRender();
        this.hot.updateData(gridData);
        this.refreshTagColumn(this, rows);
        this.hot.resumeRender();
        //重新赋值一下所有标签
        this.context.menuToolRef.current.setState({
            allRowTags: [...this.context.tagService.getAllTag("row")],
        });
        //刷新公式
        //this.context.formulaService.refreshAllPolymericRow();
        //this.context.formulaService.refreshAllPolymericColumn();
        //刷新公式@todo迁移后台
        this.formulaService.refreshAllPolymeric();
    }
    // 删除聚合列标签
    /*isAll:为true，表示设置过行聚合/列聚合操作， false：为tag标签操作
     */
    async handleDeleteJuHeColLabel(afterRemovedTagArr, isAll) {
        let { cols } = this.gridService.getRangeRowsAndColumn(this.context.state.currentRange);
        //设置行聚合重新计算了currentRange，清空的时候需要计算下rows
        if (isAll) {
            const col = this.context.state.topLeftRange?.col;
            cols = [col];
        }
        console.log(cols, "cols1111");
        const headerColumn = this.context.headerService.headerColumn;
        for (let i = 0; i < cols.length; i++) {
            const col = cols[i];
            const colData = headerColumn[col];
            const config = colData?.config;
            // 删除数组中的 对应标签
            const tag_arr = config?.c_polymeric?.tags;
            if (tag_arr && tag_arr.length > 0) {
                config.c_polymeric.tags = afterRemovedTagArr;
                // if (afterRemovedTagArr.length === 0) delete config.c_polymeric;
                let update_config_headerJson;
                if (afterRemovedTagArr &&
                    afterRemovedTagArr.length === 0 &&
                    config.c_polymeric) {
                    delete config.c_polymeric;
                }
                update_config_headerJson =
                    this.context.headerService.updateHeaderConfigByIndex(this.headerService.headJson, col, config.c_polymeric
                        ? {
                            ...config,
                            c_polymeric: config.c_polymeric,
                        }
                        : {
                            ...config,
                            c_polymeric: null,
                        });
                this.context.headerService.headerCompute(update_config_headerJson);
                let gridData = this.context.data;
                //如果聚合标签为空，重置该列为0
                if (!config.c_polymeric) {
                    this.hot.suspendRender();
                    console.log("进入条件1111");
                    for (let k = 0; k < gridData.length; k++) {
                        if (k === 0) {
                            this.hot.setDataAtCell(k, col, "");
                            gridData[k][col] = "";
                        }
                        else {
                            this.hot.setDataAtCell(k, col, 0);
                            gridData[k][col] = 0;
                        }
                    }
                    this.hot.resumeRender();
                    this.hot.updateData(gridData);
                    this.context.reloadTableDataWithStyle(gridData);
                }
            }
        }
        //重新赋值一下所有标签
        this.context.menuToolRef.current.setState({
            allColumnTags: [...this.context.tagService.getAllTag("column")],
        });
        //刷新公式
        //this.context.formulaService.refreshAllPolymericRow();
        //this.context.formulaService.refreshAllPolymericColumn();
        //刷新公式@todo迁移后台
        this.formulaService.refreshAllPolymeric(true);
    }
    // 删除聚合行标签
    /*isAll:为true，表示设置过行聚合/列聚合操作整行/整列操作， false：为标签操作，
     */
    async handleDeleteJuHeRowLabel(afterRemovedTagArr, isAll) {
        console.log(this.context.state.currentRange, "this.context.state.currentRange");
        let { rows } = this.gridService.getRangeRowsAndColumn(this.context.state.currentRange);
        //设置行聚合重新计算了currentRange，清空的时候需要计算下rows
        if (isAll) {
            const row = this.context.state.topLeftRange?.row;
            rows = [row];
        }
        let gridData = this.context.data;
        const lastHeader = this.context.headerService.lastHeader;
        //const tableColCount = lastHeader || this.context.headerService.headerColumn.length;
        for (let i = 0; i < rows.length; i++) {
            const row = rows[i];
            const config = gridData && gridData[row] && gridData[row][lastHeader]
                ? JSON.parse(gridData[row][lastHeader])
                : {};
            // 删除数组中的 对应标签
            const tag_arr = config?.r_polymeric?.tags;
            if (tag_arr && tag_arr.length > 0) {
                config.r_polymeric.tags = afterRemovedTagArr;
                if (afterRemovedTagArr.length === 0)
                    delete config.r_polymeric;
                gridData[row][lastHeader] = JSON.stringify(config);
            }
            //如果聚合标签为空，重置该列为0
            if (!config.c_polymeric) {
                this.hot.suspendRender();
                for (let k = 0; k < lastHeader; k++) {
                    const columnConfig = await this.context.headerService.getHeaderConfigByIndex(this.context.headerService.headJson, k).config;
                    const type = columnConfig && columnConfig.type ? columnConfig.type : "";
                    if (type !== "text" && k < lastHeader) {
                        console.log("进入条件", k);
                        this.hot.setDataAtCell(row, k, "");
                        gridData[row][k] = "";
                    }
                }
                this.hot.resumeRender();
            }
        }
        // 由于 cellsHook 只会合并到cellMeta ， 已有的没办法通过合并进去，所以需要重新赋值 cellMeta.
        // 批量清空cellMeta中的属性
        this.hot.suspendRender();
        const all_columns = this.headerService.headerColumn;
        for (let i = 0; i < all_columns.length; i++) {
            const colIndex = i;
            for (let j = 0; j < rows.length; j++) {
                const rowIndex = rows[j];
                if (gridData[rowIndex] && gridData[rowIndex][lastHeader]?.r_polymeric) {
                    this.hot.setCellMetaObject(rowIndex, colIndex, {
                        r_polymeric: gridData[rowIndex][lastHeader].r_polymeric,
                    });
                }
                else {
                    this.hot.removeCellMeta(rowIndex, colIndex, "r_polymeric");
                }
            }
        }
        await this.hot.resumeRender();
        console.log(gridData, "gridData after");
        //数据同步
        //this.context.data = gridData;
        this.hot.updateData(gridData);
        this.context.reloadTableDataWithStyle(gridData);
        //this.context.reloadTableData(gridData);
        //重新赋值一下所有标签
        this.context.menuToolRef.current.setState({
            allRowTags: [...this.context.tagService.getAllTag("row")],
        });
        this.refreshTagColumn(this, rows);
        //刷新公式
        //this.context.formulaService.refreshAllPolymericRow();
        //this.context.formulaService.refreshAllPolymericColumn();
        //刷新公式@todo迁移后台
        this.formulaService.refreshAllPolymeric(true);
    }
    // 删除行运算标签
    async handleDeleteRowOperatorLabel() {
        let { rows } = this.gridService.getRangeRowsAndColumn(this.context.state.currentRange);
        const gridData = this.context.data;
        const lastHeader = this.context.headerService.lastHeader;
        for (let i = 0; i < rows.length; i++) {
            const row = rows[i];
            const config = gridData && gridData[row] && gridData[row][lastHeader]
                ? JSON.parse(gridData[row][lastHeader])
                : {};
            // 删除数组中的 对应标签
            const operator_r = config?.operator_r;
            if (operator_r) {
                delete config.operator_r;
                gridData[row][lastHeader] = JSON.stringify(config);
            }
        }
        // 由于 cellsHook 只会合并到cellMeta ， 已有的没办法通过合并进去，所以需要重新赋值 cellMeta.
        // 批量清空cellMeta中的属性
        const all_columns = this.headerService.headerColumn;
        for (let i = 0; i < all_columns.length; i++) {
            const colIndex = i;
            for (let j = 0; j < rows.length; j++) {
                const rowIndex = rows[j];
                if (gridData[rowIndex] && gridData[rowIndex][lastHeader]?.operator_r) {
                    this.hot.setCellMetaObject(rowIndex, colIndex, {
                        operator_r: gridData[rowIndex][lastHeader].operator_r,
                    });
                }
                else {
                    this.hot.removeCellMeta(rowIndex, colIndex, "operator_r");
                }
            }
        }
        await this.hot.resumeRender();
        await this.hot.updateData(gridData);
    }
}
